#include "ActionManager.h"
#include <wx/log.h>
#include "../events/ActionEvent.h"

namespace Impp
{



ActionManager::ActionManager() :
	nextAxtionId(1)
{
	Start(1000,false);
}

ActionManager::~ActionManager()
{
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;
		delete cur;
		iter++;
	}
}

ActionId ActionManager::insertAction(Action* action){
	wxLogTrace(wxT("ACTION_MANAGER"), wxT("ActionManager::insertAction: inserted Action %s"),action->GetClassInfo()->GetClassName());

	ActionId id = nextAxtionId++;
	if(id < 0){
		id = nextAxtionId = 1;
	}

	action->setId(id);
	actions.push_back(action);

	ActionEvent event(action ,ACTION_EVENT_NEW_ACTION,EVT_ACTION,GetId());
	AddPendingEvent(event);

	return id;
}

void ActionManager::deleteAction(const ActionId & id, bool actionSuccess){
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;
		if(cur->getId() == id){
			if(!cur->isDeleted()){
				wxLogTrace(wxT("ACTION_MANAGER"), wxT("ActionManager::deleteAction: deleted Action %s"),cur->GetClassInfo()->GetClassName());
				ActionEvent event(cur,ACTION_EVENT_DELETE_ACTION,EVT_ACTION,GetId());
				AddPendingEvent(event);
				cur->deleteAction();
			}
			return;
		}else{
			iter++;
		}
	}
}

bool ActionManager::setActionData(const ActionId & id, const wxString & name, const int & value){
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;
		if(cur->getId() == id){
			cur->dataInt[name] = value;
			return true;
		}
		iter++;
	}
	return false;
}

int ActionManager::getActionData(const ActionId & id, const wxString & name){
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;

		if(cur->getId() == id){
			std::map<wxString,int>::iterator m = cur->dataInt.find(name);
			if(m != cur->dataInt.end()){
				return m->second;
			}else{
				return -1;
			}
		}

		iter++;
	}
	return -1;
}


void ActionManager::Notify(){
	//wxLogDebug(wxT("Action size: %i"), actions.size());

	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;

		//wxLogDebug(wxT("Action %i is Locked %i isDelted %i"), cur->getId(), cur->isLocked(), cur->isDeleted());

		if(cur->isTimedOut()){

			if(!cur->isDeleted()){
				wxLogTrace(wxT("ACTION_MANAGER"), wxT("ActionManager::deleteAction: timed out Action %s"),cur->GetClassInfo()->GetClassName());
				ActionEvent event(cur,ACTION_EVENT_DELETE_ACTION,EVT_ACTION,GetId());
				AddPendingEvent(event);
				cur->deleteAction();
			}

		}


		if(cur->isDeleted() && !cur->isLocked()){
			delete cur;
			iter = actions.erase(iter);
		}else{
			iter++;
		}



	}

}

void ActionManager::lockAction(const ActionId & id)
{
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;
		if(cur->getId() == id){
			cur->lock();
			return;
		}
		iter++;
	}
}
void ActionManager::unLockAction(const ActionId & id)
{
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;
		if(cur->getId() == id){
			cur->unLock();
			return;
		}
		iter++;
	}
}

Action* ActionManager::getAction(const wxString & actionClassName, Buddy* buddy)
{
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;
		if(!cur->isDeleted() && cur->GetClassInfo()->GetClassName() == actionClassName && cur->getBuddy() == buddy){
			return cur;
		}
		iter++;
	}
	return NULL;
}

Action* ActionManager::getAction(const ActionId & id){
	std::vector<Action*>::iterator iter(actions.begin());
	while(iter != actions.end()) {
		Action* cur = *iter;
		if(cur->getId()== id){
			return cur;
		}
		iter++;
	}
	return NULL;
}

}
